package com.authine.cloudpivot.web.api.service.impl;


import com.alibaba.dubbo.config.annotation.Reference;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.authine.cloudpivot.engine.api.facade.TaskReportFacade;
import com.authine.cloudpivot.engine.api.model.runtime.BizObjectModel;
import com.authine.cloudpivot.engine.api.model.runtime.BizObjectQueryModel;
import com.authine.cloudpivot.engine.api.model.runtime.SelectionValue;
import com.authine.cloudpivot.engine.component.query.api.FilterExpression;
import com.authine.cloudpivot.engine.component.query.api.Page;
import com.authine.cloudpivot.engine.component.query.api.helper.PageableImpl;
import com.authine.cloudpivot.engine.component.query.api.helper.Q;
import com.authine.cloudpivot.engine.enums.type.QueryDisplayType;
import com.authine.cloudpivot.web.api.dao.FASQMapper;
import com.authine.cloudpivot.web.api.dao.WHMDXXMapper;
import com.authine.cloudpivot.web.api.dubbo.DubboConfigService;
import com.authine.cloudpivot.web.api.exception.PortalException;
import com.authine.cloudpivot.web.api.service.StoreService;
import java.net.URLEncoder;

import com.authine.cloudpivot.web.api.vo.BusinessAreas;
import com.authine.cloudpivot.web.api.vo.FASQ;
import com.authine.cloudpivot.web.api.vo.FASQDETAIL;
import com.authine.cloudpivot.web.api.vo.WHMDXX;
import lombok.extern.slf4j.Slf4j;
import net.sf.json.JsonConfig;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.net.HttpURLConnection;
import java.net.URL;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.stream.Collectors;



@Slf4j
@Service
public class storeServiceImpl implements StoreService {

    @Autowired
    private WHMDXXMapper  whmdxxMapper;

    @Autowired
    private  ProjectTeamServiceImpl projectTeamServiceImpl;

    @Autowired
    private DubboConfigService dubboConfigService;

    @Autowired
    private StoreService storeService;

    @Autowired
    private FASQMapper fasqMapper;

    @Reference(version = "1.00")
    private TaskReportFacade taskReportFacade;


    /**
     * @Description : 获取已存在的编号
     * @param ： existNum
     * @author : Liun
     * @date : 2020/4/10
     */
    @Override
    public String getStoreNum(){
        String existNum=whmdxxMapper.getStoreNum();
        return existNum;
    };


    /**
     * @Description : 修改门店编号
     * @param ：
     * @author : Liun
     * @date : 2020/4/10
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateStoreNum(String objectId,String storeNum)throws PortalException{
        boolean flag= checkStoreNum(objectId,storeNum);
        if(flag){
            String staticStr="ST";
            String storeNumAfter=createStoreNum(staticStr,storeNum);
            whmdxxMapper.updateStoreNum(storeNumAfter,objectId);
        }
    };

    /**
     * @Description : 生成门店编号
     * @param ： staticStr
     * @param ： existNum
     * @author : Liun
     * @date : 2020/4/10
     */
    @Override
    public String createStoreNum(String staticStr,String existNum){
        int num = Integer.parseInt(existNum.substring(2, 8));
        num = num + 1;
        if (num < 10) {
            existNum = staticStr + "00000" + num;
        } else if (num < 100 && num>=10) {
            existNum = staticStr + "0000" + num;
        } else if (num < 1000 && num>=100) {
            existNum = staticStr + "000" + num;
        } else if (num < 10000 && num>=1000) {
            existNum = staticStr + "00" + num;
        } else if (num < 100000 && num>=1000) {
            existNum = staticStr + "0" + num;
        }else{
            existNum = staticStr+ num;
        }
        return existNum;
    }


    /**
     * @Description : 修改前先校验是否存在此门店编号
     * @param ：
     * @author : Liun
     * @date : 2020/4/10
     */
    public boolean checkStoreNum(String objectId,String storeNum)throws PortalException{
        boolean flag;
        int num=whmdxxMapper.checkStoreNum(storeNum,objectId);
        if(num==0){
            flag=false;
        }else if(num==1){
            flag=true;
        }else{
            throw new PortalException(500L, "存在多条相同门店编号，请联系管理员！");
        }
        return flag;
    }

    /**
     * @Description : 获取城市等级
     * @param ： province
     * @param ： cityName
     * @author : Liun
     * @date : 2020/4/10
     */
    @Override
   public  String getCityLevel(String province,String cityName){
        return whmdxxMapper.getCityLevel(province ,cityName);
   };

    /**
     * @Description : 根据项目和门店信息，获取当前门店督导
     * @param ： projectName
     * @param ： storeName
     * @author : Liun
     * @date : 2020/4/22
     */
    @Override
    public  String getMember(String projectName,String storeName){
        SimpleDateFormat sf=new SimpleDateFormat("yyyy-MM-dd 00:00:00");
        Date now=new Date();
        String nowTime =sf.format(now);
        String storeStatus="启用";
        String member= whmdxxMapper.getMember(projectName ,storeName,nowTime ,storeStatus);
        //生成前端能识别的对象
        String user="";
        if(StringUtils.isNotEmpty(member)){
            user= projectTeamServiceImpl.createUser(member);
        }
        return user;
    }

    @Override
    public void addStore(String id) {
        //根据id获取招聘需求提报的相关信息
        BizObjectQueryModel queryModel = new BizObjectQueryModel();
        PageableImpl pageable = new PageableImpl(0, 9999);
        queryModel.setSchemaCode("recruitmentDemand");
        queryModel.setQueryCode("recruitmentDemand");
        queryModel.setPageable(pageable);
        FilterExpression filterExpression = Q.it("id", FilterExpression.Op.Eq, id);
        queryModel.setFilterExpr(filterExpression);
        BizObjectQueryModel.Options option = new BizObjectQueryModel.Options();
        option.setQueryDisplayType(QueryDisplayType.APPEND);
        option.setCustomDisplayColumns(Arrays.asList("creater","demandDetails","projectName","projectNo"));
        queryModel.setOptions(option);
        Page<BizObjectModel> recruitmentDatas = dubboConfigService.getBizObjectFacade().queryBizObjects(queryModel);
        String userId = ((ArrayList<SelectionValue>) recruitmentDatas.getContent().get(0).getData().get("creater")).get(0).getId();
        List<Map<String,Object>> demandDetails = (ArrayList<Map<String,Object>>)recruitmentDatas.getContent().get(0).getData().get("demandDetails");
        String subjectName = (String)((HashMap<String,Object>)recruitmentDatas.getContent().get(0).getData().get("projectName")).get("id");
        String projectNo = (String)recruitmentDatas.getContent().get(0).getData().get("projectNo");

        if(demandDetails != null && demandDetails.size() > 0) {
            // 根据项目id查询所有门店
            BizObjectQueryModel queryStoreModel = new BizObjectQueryModel();
            queryStoreModel.setSchemaCode("WHMDXX");
            queryStoreModel.setQueryCode("WHMDXX");
            queryStoreModel.setPageable(pageable);
            FilterExpression storeFilter = Q.it("subjectName", FilterExpression.Op.Eq, subjectName);
            queryStoreModel.setFilterExpr(storeFilter);
            Page<BizObjectModel> storeInfoDatas = dubboConfigService.getBizObjectFacade().queryBizObjects(queryStoreModel);
            List<? extends BizObjectModel> storeModels = storeInfoDatas.getContent();
            log.error("现在userId的参数是：" + userId);
            Set<String> storeNos = storeModels.stream().map(item -> (String)item.getData().get("customerStoreNum")).collect(Collectors.toSet());
            List<Map<String,Object>> unContainsStores = demandDetails.stream().filter(item -> !storeNos.contains((String) item.get("storeCode"))).collect(Collectors.toList());
            unContainsStores.forEach(item->{
                //新增该门店信息
                BizObjectModel bizObjectModel = new BizObjectModel();
                bizObjectModel.setSchemaCode("WHMDXX");
                bizObjectModel.setFormCode("WHMDXX");
                bizObjectModel.setSequenceStatus("COMPLETED");
                Map<String, Object> data = bizObjectModel.getData();
                String name = item.get("storeName") != null ? "门店信息-" + item.get("storeName").toString() : null;
                data.put("name", name);
                data.put("customerStoreNum",item.get("storeCode"));
                data.put("customDockingPerson",item.get("storeContacts"));
                data.put("customLinkType",item.get("contactsPhone"));
                data.put("rcsArea",item.get("rcsArea"));
                data.put("area",item.get("area"));
                data.put("storeShortName", item.get("storeName"));
                data.put("cityLevel",item.get("cityType"));
                data.put("province", item.get("province"));
                data.put("cityName", item.get("city"));
                data.put("storeStatus", "启用");
                data.put("detailArea", item.get("address"));
                data.put("district", item.get("areas"));
                data.put("storeOutlet", item.get("storeChannel"));
                data.put("projectNo",projectNo);
                data.put("subjectName",subjectName);
                data.put("storeNum", getNextStoreNum());
                data.put("zpDemand",id);
                data.put("zpCount",1);
                dubboConfigService.getBizObjectFacade().saveBizObject(userId, bizObjectModel, false);
            });

            List<Map<String,Object>> containsStores = demandDetails.stream().filter(item -> storeNos.contains((String) item.get("storeCode"))).collect(Collectors.toList());
            if(CollectionUtils.isNotEmpty(containsStores)) {
                taskReportFacade.updateStoreInfo(id, subjectName, containsStores, "zp");
            }
        }
    }

    /***
     * 高德地图获取经纬度
     * @param address
     * @return
     */
    @Override
    public Map<String,String> getLatitudeAndLongitude(String address) throws UnsupportedEncodingException {
        log.info("获取经纬度开始------------------------------------");
        Map<String,String> map = new HashMap();
        String GDurl = "https://restapi.amap.com/v3/geocode/geo?address=";
        String key = "c6f5f497eeed5fdaa460bb54efcfbe10";
        address = address.trim();
        String url = GDurl + URLEncoder.encode(address, "utf-8") + "&output=JSON" + "&key="+ key;

        try {
            URL url2 = new URL(url);
            HttpURLConnection connection = (HttpURLConnection) url2.openConnection();
            connection.connect();
            // 获取输入流
            BufferedReader br = new BufferedReader(new InputStreamReader(connection.getInputStream()));
            String line;
            StringBuilder sb = new StringBuilder();
            while ((line = br.readLine()) != null) {
                sb.append(line);
            }
            br.close();
            connection.disconnect();
            JSONObject a = JSON.parseObject(sb.toString());
            JSONArray sddressArr = JSON.parseArray(a.get("geocodes").toString());
            JSONObject c = JSON.parseObject(sddressArr.get(0).toString());
            String location = c.get("location").toString();
            String longitude = location.substring(0,location.indexOf(","));
            String latitude = location.substring(longitude.length()+1, location.length());
            map.put("longitude",longitude);
            map.put("latitude",latitude);
            log.info("获取经纬度结束------------------------------------");
            return map;
        } catch (Exception e) {
            e.printStackTrace();
            log.info("获取经纬度失败------------------------------------");
            return map;
        }

    }

    /***
     * 经纬度获取商圈
     * @param bc
     * @return
     */
    public List<BusinessAreas> getSQ(String bc) throws UnsupportedEncodingException {
        log.info("获取商圈开始------------------------------------");
        String GDurl = "https://restapi.amap.com/v3/geocode/regeo?location=";
        String key = "c6f5f497eeed5fdaa460bb54efcfbe10";
        bc = bc.trim();
        String url = GDurl + URLEncoder.encode(bc, "utf-8") + "&output=JSON" + "&key="+ key;
        List<BusinessAreas> list = new ArrayList<>();
        try {
            URL url2 = new URL(url);
            HttpURLConnection connection = (HttpURLConnection) url2.openConnection();
            connection.connect();
            // 获取输入流
            BufferedReader br = new BufferedReader(new InputStreamReader(connection.getInputStream()));
            String line;
            StringBuilder sb = new StringBuilder();
            while ((line = br.readLine()) != null) {
                sb.append(line);
            }
            br.close();
            connection.disconnect();
            JSONObject a = (JSONObject) JSON.parseObject(sb.toString()).get("regeocode");
            JSONObject b = (JSONObject) a.get("addressComponent");
            String as = b.get("businessAreas").toString();
            JSONArray sddressArr = JSON.parseArray(b.get("businessAreas").toString());
            if(as.equals("[[]]")){
                log.info("获取商圈结束------------------------------------");
                return new ArrayList<>();
            }
            list = (List<BusinessAreas>) net.sf.json.JSONArray.
                    toCollection(net.sf.json.JSONArray.fromObject(sddressArr), BusinessAreas.class);
            log.info("获取商圈结束------------------------------------");
            return list;
        } catch (Exception e) {
            e.printStackTrace();
            log.info("获取商圈失败------------------------------------");
    }
        return list;
    }

    /***
     * 定时任务-高德地图根据经纬度获取商圈 （废弃）
     * @param
     * @return
     */
    @Override
    //@Scheduled(cron = "0 0/30 * * * ?")
    public void getBusinessCircle() throws UnsupportedEncodingException {
        log.info("定时插入经纬度、商圈开始执行------------------------------------");
        //查询门店获取没有经纬度的数据、并调用高德地图获取经纬度写入该门店对应字段
        List<WHMDXX> list = whmdxxMapper.selectList();
        if(list.isEmpty()){
            return;
        }
        for(WHMDXX whmdxx : list){
            if(StringUtils.isEmpty(whmdxx.getProvince()) || StringUtils.isEmpty(whmdxx.getCityName())
                    || StringUtils.isEmpty(whmdxx.getDetailArea())){
                continue;
            }
            StringBuilder sb = new StringBuilder();
            sb.append(whmdxx.getProvince()).append(whmdxx.getCityName()).append(whmdxx.getDistrict()).append(whmdxx.getDetailArea());
            Map<String,String> map = getLatitudeAndLongitude(sb.toString());
            if(map.isEmpty()){
                continue;
            }
            whmdxxMapper.updateLongitudeLatitude(whmdxx.getId(),map.get("longitude"),map.get("latitude"),null);
        }
        //查询门店获取没有商圈的数据，调用高德获取所在商圈
        //将获取所有商圈存到商圈表中，将返回的第一条存入门店表中
        List<WHMDXX> listSssq = whmdxxMapper.selectListForSssq();
        if(listSssq.isEmpty()){
            return;
        }
        for(WHMDXX whmdxx : listSssq){
            if(StringUtils.isEmpty(whmdxx.getLongitude()) || StringUtils.isEmpty(whmdxx.getLatitude())){
                continue;
            }
            StringBuilder sb = new StringBuilder();
            sb.append(whmdxx.getLongitude()).append(",").append(whmdxx.getLatitude());
            List<BusinessAreas> jwd = getSQ(sb.toString());
            if(!jwd.isEmpty()){
                    //先根据省市区 和商圈 进行查询，没有重复的插入---将所有商圈插入进商圈表，然后将门店表中的数据插入对应的子表中
                    int i = 0;
                    for (BusinessAreas ba : jwd) {
                        FASQ fasq = fasqMapper.selectFASQ(ba.getName(), whmdxx.getProvince(), whmdxx.getCityName());
                        if (null != fasq) {
                            if (i == 0) {//只存第一条
                                whmdxxMapper.updateLongitudeLatitude(whmdxx.getId(), null, null, fasq.getId());
                                WHMDXX whm = whmdxxMapper.selectForpcs(whmdxx.getId());
                                //查询这个商圈对应的门店表
                                createFasqDetail(ba.getName(), fasq.getId(), whm);
                                i++;
                            }
                            //统计门店数，和项目数
                            int mds = fasqMapper.selectFASQCountMDS(fasq.getId());
                            int xms = fasqMapper.selectFASQCountXMS(fasq.getId());
                            fasqMapper.updateFASQMDSXMS(mds + "", xms + "", fasq.getId(), null);
                        } else {
                            WHMDXX whm = whmdxxMapper.selectForpcs(whmdxx.getId());
                            //没有-插商圈表
                            FASQ fasq1 = new FASQ();
                            fasq1.setId(UUID.randomUUID().toString().replaceAll("\\-", ""));
                            fasq1.setSequenceStatus("COMPLETED");
                            fasq1.setCreater(whm.getCreater());
                            fasq1.setCreatedDeptId(whm.getCreateddeptid());
                            fasq1.setOwner(whm.getOwner());
                            fasq1.setOwnerDeptId(whm.getOwnerdeptid());
                            fasq1.setCreatedTime(new Date());
                            //FA-编码
                            Integer num = fasqMapper.selectFASQCount();
                            if(num == null){
                                num = 0;
                            }
                            fasq1.setFabm("P" + String.format("%06d", num + 1));

                            fasq1.setSf(whm.getProvince());//省
                            fasq1.setCs(whm.getCityName());//市
                            fasq1.setQx(whm.getDistrict());//区
                            //经纬度
                            String loca = ba.getLocation();
                            if (StringUtils.isNotEmpty(loca)) {
                                String longitude = loca.substring(0, loca.indexOf(","));
                                String latitude = loca.substring(longitude.length() + 1, loca.length());
                                fasq1.setJd(longitude);
                                fasq1.setWd(latitude);
                            }
                            fasq1.setSqm(ba.getName());//商圈名
                            fasqMapper.insertFasq(fasq1);
                            if (i == 0) {//只存第一条
                                whmdxxMapper.updateLongitudeLatitude(whmdxx.getId(), null, null, fasq1.getId());
                                WHMDXX whm1 = whmdxxMapper.selectForpcs(whmdxx.getId());
                                //查询这个商圈对应的门店表
                                createFasqDetail(ba.getName(), fasq1.getId(), whm1);
                                i++;
                            }
                            //统计门店数，和项目数
                            int mds = fasqMapper.selectFASQCountMDS(fasq1.getId());
                            int xms = fasqMapper.selectFASQCountXMS(fasq1.getId());

                            fasqMapper.updateFASQMDSXMS(mds + "", xms + "", fasq1.getId(), num + 1);
                        }
                    }

            }
        }
        log.info("定时插入经纬度、商圈执行完毕！");
    }

    /***
     * 修改门店中的商圈
     * @param
     * @param
     * @param
     */
    @Override
    public String updateSQ(String mdid, String updateId){
        String str = "数据没有变化，不用修改";
        WHMDXX whm1 = whmdxxMapper.selectForpcs(mdid);
//        whmdxxMapper.updateLongitudeLatitude(mdid,null,null,updateId);
        if(updateId.isEmpty()){
            return str;
        }
        if(StringUtils.isEmpty(whm1.getSssq())){
            if(whm1.getSssq().equals(updateId)){
                return str;
            }
            //如果一开始没有关联商圈
            createFasqDetail("",updateId,whm1);
        }else{
            //有关联商圈
            FASQDETAIL fasqdetail = fasqMapper.selectFASQDETAIL(whm1.getSssq(),mdid);
            if(fasqdetail != null){
                fasqMapper.updateFASQDETAIL(fasqdetail.getId(),updateId);
                //统计门店数，和项目数,-1
                int mds = fasqMapper.selectFASQCountMDS(whm1.getSssq());
                int xms = fasqMapper.selectFASQCountXMS(whm1.getSssq());
                fasqMapper.updateFASQMDSXMS(mds+"",xms+"",whm1.getSssq(),null);
            }else{
                createFasqDetail("",updateId,whm1);
            }
        }
        //统计门店数，和项目数 +1
        int mds = fasqMapper.selectFASQCountMDS(updateId);
        int xms = fasqMapper.selectFASQCountXMS(updateId);
        fasqMapper.updateFASQMDSXMS(mds+"",xms+"",updateId,null);
        log.info("修改商圈完毕！");
        return "修改成功";
    }

    public void createFasqDetail(String sqName,String parentId,WHMDXX whm){
        if(sqName == null){
            return;
        }
        if(whm!=null){
            FASQDETAIL fasqdetail = new FASQDETAIL();
            fasqdetail.setMdid(whm.getId());
            fasqdetail.setParentId(parentId);
            fasqdetail.setDpbh(whm.getStorenum());//店铺编号;
            fasqdetail.setXmmc(whm.getSubjectName());//项目名称
            fasqdetail.setDpmc(whm.getStoreshortname());  //店铺名称
            fasqdetail.setXxdz(whm.getDetailArea());//详细地址
            fasqdetail.setQyrcs(whm.getRcsarea());    //区域（RCS）
            fasqdetail.setId(UUID.randomUUID().toString().replaceAll("\\-", ""));
            fasqMapper.insertFasqDetail(fasqdetail);
        }
    }

    @Override
    public String getNextStoreNum(){
        String staticStr = "ST";
        String existNum= storeService.getStoreNum();
        if (StringUtils.isEmpty(existNum)) {
            existNum = "ST000001";
        } else {
            existNum= storeService.createStoreNum(staticStr, existNum);
        }
        return existNum;
    }


}



